﻿using System;
using Microsoft.Xna.Framework;

namespace SuperRyoninRPG.Main
{
	public static class RectangleExtensions
	{
		/// <summary>
		///     2 つの矩形が交差する符号付き深度を計算します。
		/// </summary>
		/// <returns>
		///     交差する 2 つの矩形の重なりの量。これらの深度値は
		///     矩形が交差する幅によっては負になる可能性があります。
		///     これにより、呼び出し側は、衝突を解決するためにオブジェクトを
		///     押し出す適切な方向を決定できます。矩形が交差しない場合、Vector2.Zero が
		///     返されます。
		/// </returns>
		public static Vector2 GetIntersectionDepth(this Rectangle rectA, Rectangle rectB)
		{
			// 半分のサイズを計算します。
			float halfWidthA = rectA.Width / 2.0f;
			float halfHeightA = rectA.Height / 2.0f;
			float halfWidthB = rectB.Width / 2.0f;
			float halfHeightB = rectB.Height / 2.0f;

			// 中心を計算します。
			var centerA = new Vector2(rectA.Left + halfWidthA, rectA.Top + halfHeightA);
			var centerB = new Vector2(rectB.Left + halfWidthB, rectB.Top + halfHeightB);

			// 中心間の現在の距離と交差しない最小距離を計算します。
			float distanceX = centerA.X - centerB.X;
			float distanceY = centerA.Y - centerB.Y;
			float minDistanceX = halfWidthA + halfWidthB;
			float minDistanceY = halfHeightA + halfHeightB;

			// まったく交差しない場合、(0, 0) を返します。
			if (Math.Abs(distanceX) >= minDistanceX || Math.Abs(distanceY) >= minDistanceY)
			{
				return Vector2.Zero;
			}

			// 交差深度を計算して、返します。
			float depthX = distanceX > 0 ? minDistanceX - distanceX : -minDistanceX - distanceX;
			float depthY = distanceY > 0 ? minDistanceY - distanceY : -minDistanceY - distanceY;
			return new Vector2(depthX, depthY);
		}

		/// <summary>
		///     矩形の下端の中心の位置を取得します。
		/// </summary>
		public static Vector2 GetBottomCenter(this Rectangle rect)
		{
			return new Vector2(rect.X + rect.Width / 2.0f, rect.Bottom);
		}
	}
}